﻿using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.GamerServices;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Media;
using AfterCaveStory.Objetos.Platformer.Personagens;

namespace AfterCaveStory
{

    class Personagem : PhysicsObject
    {

        public enum States 
        {
            ANDANDO,
            ANDANDO_CIMA,
            PULANDO,
            PULANDO_CIMA,
            PULANDO_BAIXO,
            PARADO,
            PARADO_CIMA,
        }

        States state = States.PARADO;

        public Personagem(Texture2D textura, Nullable<Rectangle> sourceRectangle, float depth)
            : base(textura, sourceRectangle, depth)
        {
            #region Animações
            AnimationStructure andando = new AnimationStructure();
            andando.name = "andando";
            andando.frameCount = 3;
            andando.X = 0;
            andando.Y = 0;
            andando.framesPerSecond = 6;
            if (sourceRectangle != null)
            {
                Rectangle rectangle = (Rectangle)sourceRectangle;
                andando.frameWidth = rectangle.Width;
                andando.frameHeight = rectangle.Height;
            }
            else
            {
                andando.frameWidth = textura.Width;
                andando.frameHeight = textura.Height;
            }
            addAnimation(andando);

            AnimationStructure andandoCima = new AnimationStructure();
            andandoCima.name = "andandoCima";
            andandoCima.frameCount = 3;
            andandoCima.X = 96;
            andandoCima.Y = 0;
            andandoCima.framesPerSecond = 6;
            if (sourceRectangle != null)
            {
                Rectangle rectangle = (Rectangle)sourceRectangle;
                andandoCima.frameWidth = rectangle.Width;
                andandoCima.frameHeight = rectangle.Height;
            }
            else
            {
                andandoCima.frameWidth = textura.Width;
                andandoCima.frameHeight = textura.Height;
            }
            addAnimation(andandoCima);

            AnimationStructure parado = new AnimationStructure();
            parado.name = "parado";
            parado.frameCount = 1;
            parado.X = 0;
            parado.Y = 0;
            parado.framesPerSecond = 6;
            if (sourceRectangle != null)
            {
                Rectangle rectangle = (Rectangle)sourceRectangle;
                parado.frameWidth = rectangle.Width;
                parado.frameHeight = rectangle.Height;
            }
            else
            {
                parado.frameWidth = textura.Width;
                parado.frameHeight = textura.Height;
            }
            addAnimation(parado);

            AnimationStructure pulando = new AnimationStructure();
            pulando.name = "pulando";
            pulando.frameCount = 1;
            pulando.X = 32;
            pulando.Y = 0;
            pulando.framesPerSecond = 6;
            if (sourceRectangle != null)
            {
                Rectangle rectangle = (Rectangle)sourceRectangle;
                pulando.frameWidth = rectangle.Width;
                pulando.frameHeight = rectangle.Height;
            }
            else
            {
                pulando.frameWidth = textura.Width;
                pulando.frameHeight = textura.Height;
            }
            addAnimation(pulando);

            AnimationStructure pulandoCima = new AnimationStructure();
            pulandoCima.name = "pulandoCima";
            pulandoCima.frameCount = 1;
            pulandoCima.X = 128;
            pulandoCima.Y = 0;
            pulandoCima.framesPerSecond = 6;
            if (sourceRectangle != null)
            {
                Rectangle rectangle = (Rectangle)sourceRectangle;
                pulandoCima.frameWidth = rectangle.Width;
                pulandoCima.frameHeight = rectangle.Height;
            }
            else
            {
                pulandoCima.frameWidth = textura.Width;
                pulandoCima.frameHeight = textura.Height;
            }
            addAnimation(pulandoCima);

            AnimationStructure pulandoBaixo = new AnimationStructure();
            pulandoBaixo.name = "pulandoBaixo";
            pulandoBaixo.frameCount = 1;
            pulandoBaixo.X = 192;
            pulandoBaixo.Y = 0;
            pulandoBaixo.framesPerSecond = 6;
            if (sourceRectangle != null)
            {
                Rectangle rectangle = (Rectangle)sourceRectangle;
                pulandoBaixo.frameWidth = rectangle.Width;
                pulandoBaixo.frameHeight = rectangle.Height;
            }
            else
            {
                pulandoBaixo.frameWidth = textura.Width;
                pulandoBaixo.frameHeight = textura.Height;
            }
            addAnimation(pulandoBaixo);

            AnimationStructure paradoCima = new AnimationStructure();
            paradoCima.name = "paradoCima";
            paradoCima.frameCount = 1;
            paradoCima.X = 96;
            paradoCima.Y = 0;
            paradoCima.framesPerSecond = 6;
            if (sourceRectangle != null)
            {
                Rectangle rectangle = (Rectangle)sourceRectangle;
                paradoCima.frameWidth = rectangle.Width;
                paradoCima.frameHeight = rectangle.Height;
            }
            else
            {
                paradoCima.frameWidth = textura.Width;
                paradoCima.frameHeight = textura.Height;
            }
            addAnimation(paradoCima);

            #endregion

            Animation = "pulando";
        }

        public override void update(World world)
        {
            verifyMovement();
            verifyJump();
            verifyTiro(world);
            verifyStates();
            updateAnimation();

            Console.WriteLine(Animation);
            base.update(world);
        }

        public void verifyMovement()
        {
            if (Controller.KeyDown(Keys.Left))
            {
                velocity.X += -aceleration;
                inverted = false;

                if (onGround)
                {
                    if (Controller.KeyDown(Keys.Up))
                    {
                        state = States.ANDANDO_CIMA;
                    }
                    else
                    {
                        state = States.ANDANDO;
                    }
                }
            }
            else if (Controller.KeyDown(Keys.Right))
            {
                velocity.X += aceleration;
                inverted = true;


                if (onGround)
                {
                    if (Controller.KeyDown(Keys.Up))
                    {
                        state = States.ANDANDO_CIMA;
                    }
                    else
                    {
                        state = States.ANDANDO;
                    }
                }  
            }


        }

        private void verifyStates()
        {
            if (velocity.X == 0 && onGround)
            {
                if (Controller.KeyDown(Keys.Up))
                {
                    state = States.PARADO_CIMA;
                }
                else
                {
                    state = States.PARADO;
                }
            }

            if (!onGround)
            {

                if (Controller.KeyDown(Keys.Up))
                {
                    state = States.PULANDO_CIMA;
                }
                else if (Controller.KeyDown(Keys.Down))
                {
                    Console.WriteLine("oi");
                    state = States.PULANDO_BAIXO;
                }
                else
                {
                    state = States.PULANDO;
                }

            }
        }

        public void verifyJump()
        {
            if ((Controller.KeyPressed(Keys.Z)) && (onGround))
            {
                velocity.Y = -10.5f;
            }
        }

        private void verifyTiro(World world)
        {
            if (Controller.KeyPressed(Keys.X))
            {
                if (state == States.PARADO_CIMA || state == States.ANDANDO_CIMA || state == States.PULANDO_CIMA)
                {
                    Tiro tiro = new Tiro(Game1.Self.Content.Load<Texture2D>("tiro"), null, 0.5f, this.x, this.y, 270);
                    tiro.setarPontoDeReferencia(PontoDeReferencia.CENTRO);
                    tiro.rotation = 270;
                    world.createObject(tiro);
                }
                else if (state == States.PULANDO_BAIXO)
                {
                    Tiro tiro = new Tiro(Game1.Self.Content.Load<Texture2D>("tiro"), null, 0.5f, this.x, this.y, 90);
                    tiro.setarPontoDeReferencia(PontoDeReferencia.CENTRO);
                    tiro.rotation = 90;
                    world.createObject(tiro);
                }
                else if (inverted)
                {
                    Tiro tiro = new Tiro(Game1.Self.Content.Load<Texture2D>("tiro"), null, 0.5f, this.x, this.y, 0);
                    tiro.setarPontoDeReferencia(PontoDeReferencia.CENTRO);
                    world.createObject(tiro);
                }
                else
                {
                    Tiro tiro = new Tiro(Game1.Self.Content.Load<Texture2D>("tiro"), null, 0.5f, this.x, this.y, 180);
                    tiro.setarPontoDeReferencia(PontoDeReferencia.CENTRO);
                    world.createObject(tiro);
                }
                
            }
        }

        public void updateAnimation()
        {
            switch (state)
            {
                case States.ANDANDO: Animation = "andando"; break;
                case States.ANDANDO_CIMA: Animation = "andandoCima"; break;
                case States.PARADO: Animation = "parado"; break;
                case States.PARADO_CIMA: Animation = "paradoCima"; break;
                case States.PULANDO: Animation = "pulando"; break;
                case States.PULANDO_CIMA: Animation = "pulandoCima"; break;
                case States.PULANDO_BAIXO: Animation = "pulandoBaixo"; break;
            }  
        }

        protected override void handleBeginGroundContact()
        {
            state = States.PARADO;
        }
    }
}
